package jmine.tec.hydra;

import java.io.ByteArrayInputStream;
import java.io.InputStream;
import java.util.HashMap;
import java.util.Map;

import jmine.tec.hydra.api.HydraMessage;
import jmine.tec.hydra.api.MessageDirection;
import jmine.tec.hydra.domain.HydraRequestImpl;
import jmine.tec.hydra.domain.HydraSystem;
import jmine.tec.hydra.script.DecodeResult;
import jmine.tec.hydra.script.DecodeScriptContext;
import jmine.tec.script.persistent.domain.Script;
import bancosys.tec.persist.controller.PersistenceEnabledController;
import bancosys.tec.persist.dao.BaseDAO;

/**
 * Executor mock de scripts de decode, deve ser utilizado para efetuar testes unitários destes scripts.
 * 
 * @author lundberg
 */
public class MockDecodeScriptRunner {

    private HydraController controller;

    /**
     * @param controller
     */
    public MockDecodeScriptRunner(HydraController controller) {
        super();
        this.controller = controller;
    }

    /**
     * @param controller
     */
    public MockDecodeScriptRunner(PersistenceEnabledController controller) {
        super();
        BaseDAO<HydraSystem> dao = controller.getDAOFactory().getGenericDAO(HydraSystem.class);
        this.controller = (HydraController) dao.createBean().getController();
    }

    public DecodeResult run(String mnemonico, String message) throws Throwable {
        return this.run(mnemonico, message, new HashMap<String, String>());
    }

    public DecodeResult run(String mnemonico, String messageBody, Map<String, String> messageProperties) throws Throwable {
        return this.run(mnemonico, new ByteArrayInputStream(messageBody.getBytes("UTF-8")), messageProperties);
    }

    /**
     * Executa o script com o mnemônico dado e a mensagem dada
     * 
     * @param mnemonico mnemonico
     * @param message message
     * @return DecodeResult
     * @throws Throwable Throwable
     */
    public DecodeResult run(String mnemonico, InputStream message) throws Throwable {
        return this.run(mnemonico, message, new HashMap<String, String>());
    }

    /**
     * Executa o script com o mnemônico dado e a mensagem e propriedades dada
     * 
     * @param mnemonico mnemonico
     * @param message message
     * @return DecodeResult
     * @throws Throwable Throwable
     */
    public DecodeResult run(String mnemonico, InputStream messageBody, Map<String, String> messageProperties) throws Throwable {
        HydraMessage message =
                this.controller.getProvider().createMessage(new HydraRequestImpl(), MessageDirection.RECEIVED, messageBody,
                        messageProperties);
        BaseDAO<Script> dao = this.controller.getDAOFactory().getGenericDAO(Script.class);
        Script script = dao.findByNaturalKey(mnemonico);
        return script.createContext(DecodeScriptContext.class).prepare(message).dispatchExecution();
    }

}
